//
// Created by Administrator on 2020/7/11.
//T6章:数组、指针与字符串(2)
//对象复制与移动
//1.深层复制与浅层复制
//浅层复制:实现对象数据元素的一一对应复制
//深层复制:当被复制的对象数据成员是指针类型时,不是复制该指针成员本身
//       而是将指针所指的对象进行复制
/*
#include <iostream>
#include <cassert>
using namespace std;
class Point
{
public:
    Point():x(0),y(0)
    {
        cout<<"Default Constructor called."<<endl;
    }
    Point(int x,int y):x(x),y(y){cout<<"Constructor called."<<endl;}
    ~Point(){cout<<"Destructor called."<<endl;}
    int getX()const{return x;}
    int getY()const{return y;}
    void move(int newX,int newY)
    {
        x=newX;
        y=newY;
    }
private:
    int x,y;
};

class ArrayOfPoints
{
public:
    ArrayOfPoints(int size):size(size)
    {
        points=new Point[size];
    }
    ~ArrayOfPoints() {
        cout << "Deleting..." << endl;
        delete[] points;
    }
    Point& element(int index) {
        assert(index >= 0 && index < size);
        return points[index];
    }
private:
    Point *points;//调用动态数组首地址
    int size;//数组大小
};
//以上与前一致
int main()
{
    int count;
    cout<<"Please enter the count of points:";
    cin>>count;
    ArrayOfPoints pointsArray1(count);//创建对象数组
    pointsArray1.element(0).move(5,10);
    pointsArray1.element(1).move(15,20);

    ArrayOfPoints pointsArray2(pointsArray1);//创建副本

    cout<<"Copy of pointsArray1:"<<endl;
    cout<<"Point_0 of array2:"<<pointsArray2.element(0).getX()<<","
    <<pointsArray2.element(0).getY()<<endl;
    cout<<"Point_1 of array2:"<<pointsArray2.element(1).getX()<<","
        <<pointsArray2.element(1).getY()<<endl;

    pointsArray1.element(0).move(25,30);
    pointsArray1.element(1).move(35,40);
    cout<<"After the moving of pointsArray1:"<<endl;

    cout<<"Point_0 of array2:"<<pointsArray2.element(0).getX()<<","
    <<pointsArray2.element(0).getY()<<endl;
    cout<<"Point_1 of array2:"<<pointsArray2.element(1).getX()<<","
        <<pointsArray2.element(1).getY()<<endl;

    return 0;
}
*/
//================以上程序有问题（见T66.Md）==============
//以下为改造
/*
#include <iostream>
#include <cassert>
using namespace std;
class Point
{
public:
    Point():x(0),y(0)
    {
        cout<<"Default Constructor called."<<endl;
    }
    Point(int x,int y):x(x),y(y){cout<<"Constructor called."<<endl;}
    ~Point(){cout<<"Destructor called."<<endl;}
    int getX()const{return x;}
    int getY()const{return y;}
    void move(int newX,int newY)
    {
        x=newX;
        y=newY;
    }
private:
    int x,y;
};

class ArrayOfPoints{
public:
    ArrayOfPoints(int size):size(size)
    {
        points=new Point[size];
    }
    ~ArrayOfPoints() {
        cout << "Deleting..." << endl;
        delete[] points;
    }
    Point& element(int index) {
        assert(index >= 0 && index < size);
        return points[index];
    }
    ArrayOfPoints(const ArrayOfPoints& pointsArray);//Add
private:
    Point *points;//调用动态数组首地址
    int size;//数组大小
//其他同上
};
ArrayOfPoints::ArrayOfPoints(const ArrayOfPoints& v)
{
    size=v.size;
    points=new Point[size];
    for(int i=0;i<size;i++)
        points[i]=v.points[i];
}
int main()
{
    int count;
    cout<<"Please enter the count of points:";
    cin>>count;
    ArrayOfPoints pointsArray1(count);//创建对象数组
    pointsArray1.element(0).move(5,10);
    pointsArray1.element(1).move(15,20);

    ArrayOfPoints pointsArray2(pointsArray1);//创建副本

    cout<<"Copy of pointsArray1:"<<endl;
    cout<<"Point_0 of array2:"<<pointsArray2.element(0).getX()<<","
        <<pointsArray2.element(0).getY()<<endl;
    cout<<"Point_1 of array2:"<<pointsArray2.element(1).getX()<<","
        <<pointsArray2.element(1).getY()<<endl;

    pointsArray1.element(0).move(25,30);
    pointsArray1.element(1).move(35,40);
    cout<<"After the moving of pointsArray1:"<<endl;

    cout<<"Point_0 of array2:"<<pointsArray2.element(0).getX()<<","
        <<pointsArray2.element(0).getY()<<endl;
    cout<<"Point_1 of array2:"<<pointsArray2.element(1).getX()<<","
        <<pointsArray2.element(1).getY()<<endl;

    return 0;
}
*/
//2.移动构造
//-C++11引入移动语义:源对象资源的控制权全部交给目标对象
//移动构造函数：class_name(class_name &&)
//V1:使用深层复制构造函数(返回时构造临时对象,动态分配将临时对象返回到主调函数,然后删除临时对象)
//V2:使用移动构造函数(将要返回的局部对象转移到主调函数,省去了构造和删除临时对象的过程)
/*-----------------V1-----------------
#include <iostream>
using namespace std;
class IntNum
{
public:
    IntNum(int x=0):xptr(new int(x))//构造函数
    {
        cout<<"Calling constructor..."<<endl;
    }
    IntNum(const IntNum & n):xptr(new int(*n.xptr))//复制构造函数
    {
        cout<<"Calling copy constructor..."<<endl;
    };
    ~IntNum()//析构函数
    {
        delete xptr;
        cout<<"Destructing..."<<endl;
    }
    int getInt(){return *xptr;}
private:
    int *xptr;
};
//返回值为IntNum类对象
IntNum getNum()
{
    IntNum a;
    return a;
}
int main()
{
    cout<<getNum().getInt()<<endl;
    return 0;
}
*/
//-----------------V2-----------------
#include <iostream>
using namespace std;
class IntNum
{
public:
    IntNum(int x=0):xptr(new int(x))//构造函数
    {
        cout<<"Calling constructor..."<<endl;
    }
    IntNum(const IntNum & n):xptr(new int(*n.xptr))//复制构造函数
    {
        cout<<"Calling copy constructor..."<<endl;
    };
    IntNum(IntNum && n):xptr(n.xptr)//移动构造函数(&&是右值引用)
    {
        n.xptr= nullptr;
        cout<<"Calling move constructor..."<<endl;
    }
    ~IntNum()//析构函数
    {
        delete xptr;
        cout<<"Destructing..."<<endl;
    }
    int getInt(){return *xptr;}
private:
    int *xptr;
};
//返回值为IntNum类对象
IntNum getNum()
{
    IntNum a;
    return a;
}
int main()
{
    cout<<getNum().getInt()<<endl;
    return 0;
}




